import threading
import time

from channels.generic.websocket import WebsocketConsumer
from django.core.cache import cache

from pms import utils

run_flag, ack = False, False


def print_thread_id():
    """打印线程id"""
    t = threading.currentThread()
    print('Thread id : %d' % t.ident)


def bold_fmt(s):
    """加粗"""
    return "<b>{}</b>".format(s)


def bold_time(s):
    """时间字符串加粗分秒
    20211202091356435
    """
    s1 = s[:-7]
    s2 = s[-7:-3]
    s3 = s[-3:]
    return "{}<b>{}</b>{}".format(s1, s2, s3)


def idx_tgt(i, qc):
    """i索引，qc指标个数"""
    res = 1
    if i > 7:
        res = (i - 7) % (qc + 1)
    return res


def fmt_log(consumer, msg):
    """格式化模拟数据显示
    index = 7 + n*(qc + 1)
    (index - 7)/(qc + 1)
    """
    res = []
    bl = [3, 5, 6, 7]
    sl = msg.split(utils.PTN.COMMA)
    qc = int(sl[6])
    for i in range(len(sl)):
        s = sl[i]
        if i == 1:
            res.append(bold_time(s))
        elif i in bl or idx_tgt(i, qc) == 0:
            res.append(bold_fmt(s))
        else:
            res.append(s)
    msg = utils.PTN.COMMA.join(res)
    consumer.send(msg)


class LogConsumer(WebsocketConsumer):
    """实时查看模拟数据"""

    thread_list = []

    def connect(self):
        self.accept()

    def disconnect(self, close_code):
        self.force_close()

    def receive(self, **kwargs):
        global run_flag, ack
        param = kwargs['text_data']
        if param == 'close_log':
            run_flag = False
            while True:
                if ack:
                    self.force_close()
                    break
                time.sleep(0.1)
        if param == 'view_log':
            utils.FakeUtil.init()
            conf_list = utils.FakeUtil.get_conf_list()
            if len(conf_list) != 0:
                run_flag = True
                for conf in conf_list:
                    self.thread_list.append(MyThread(self, conf))
                for th in self.thread_list:
                    th.start()
                cache.set('exec-user', cache.get('conf-user'))
            else:
                self.send('no_tgt_config')
        if param == 'force_close':
            self.force_close()

    def force_close(self):
        for th in self.thread_list:
            th.stop()
        self.thread_list.clear()
        self.close()
        cache.delete('exec-user')


class MyThread(threading.Thread):
    """自定义线程类，指定频率向 RabbitMQ 发送消息"""

    def __init__(self, consumer, conf):
        threading.Thread.__init__(self)
        self.msg_util = utils.MsgUtil(conf)
        self.consumer = consumer
        self.interval = conf[utils.PTN.ITL] * 1000 * 1000
        self.__running = threading.Event()
        self.__running.set()
        self._stop_event = threading.Event()
        self.util = utils.FakeUtil()

    def run(self):
        global run_flag, ack
        last_time = 0
        while self.__running.isSet():
            msg = self.msg_util.msg()
            this_time = time.time_ns()
            diff_time = this_time - last_time
            if diff_time < self.interval:
                delay = (self.interval - diff_time) / (1000 * 1000 * 1000)
                time.sleep(delay)
                msg = self.msg_util.msg()
            if run_flag:
                fmt_log(self.consumer, msg)
                self.util.send_to_rabbitmq(msg)
                last_time = time.time_ns()
                ack = False
            else:
                ack = True

    def stop(self):
        self.__running.clear()
        self._stop_event.set()
